/*
 * @Author: 0x9DEFA478
 * @Date: 2025-08-09 22:28:59
 * @LastEditTime: 2025-10-06 21:30:07
 * @LastEditors: 0x9DEFA478
 * @Description: 
 * 
 */
#ifndef hH_Iterator_HPP_
#define hH_Iterator_HPP_
#include <type_traits>
#if __cplusplus >= 202000L
#include <concepts>
#endif




namespace H{

  namespace Iterator{

    template<typename Type>
    class Array{
      public:
        explicit Array(Type* pointer)noexcept:pointer(pointer){}
        ~Array()noexcept=default;

        Array(const Array&)noexcept=default;
        Array(Array&&)noexcept=default;

        Type* GetPointer()const noexcept{return pointer;}
        Type* operator->()const noexcept{return pointer;}

        Type& operator*()const noexcept{return *pointer;}

        Array operator++(int)noexcept{Array r(pointer);pointer++;return r;}
        Array& operator++()noexcept{pointer++;return *this;}
        Array operator--(int)noexcept{Array r(pointer);pointer--;return r;}
        Array& operator--()noexcept{pointer--;return *this;}

#if __cplusplus >= 202000L
        template<typename T>
        requires std::same_as<std::remove_cv_t<Type>,std::remove_cv_t<T>>
        bool operator==(const Array<T>& iterator)const noexcept{return this->pointer==iterator.GetPointer();}
        template<typename T>
        requires std::same_as<std::remove_cv_t<Type>,std::remove_cv_t<T>>
        bool operator!=(const Array<T>& iterator)const noexcept{return this->pointer!=iterator.GetPointer();}
#else
        template<typename T>
        std::enable_if_t<std::is_same_v<std::remove_cv_t<Type>,std::remove_cv_t<T>>,bool> operator==(const Array<T>& iterator)const noexcept{return this->pointer==iterator.GetPointer();}
        template<typename T>
        std::enable_if_t<std::is_same_v<std::remove_cv_t<Type>,std::remove_cv_t<T>>,bool> operator!=(const Array<T>& iterator)const noexcept{return this->pointer!=iterator.GetPointer();}
#endif

      protected:
        Type* pointer;
    };

    template<typename Type>
    class Reverse_Array:public Array<Type>{
      public:
        explicit Reverse_Array(Type* pointer)noexcept:Reverse_Array::Array(pointer){}
        ~Reverse_Array()noexcept=default;

        Reverse_Array(const Reverse_Array&)noexcept=default;
        Reverse_Array(Reverse_Array&&)noexcept=default;

        Reverse_Array operator++(int)noexcept{Reverse_Array r(this->pointer);this->pointer--;return r;}
        Reverse_Array& operator++()noexcept{this->pointer--;return *this;}
        Reverse_Array operator--(int)noexcept{Reverse_Array r(this->pointer);this->pointer++;return r;}
        Reverse_Array& operator--()noexcept{this->pointer++;return *this;}
        
    };

  }

}




#endif //hH_Iterator_HPP_
